{
 "cells": [
  {
   "cell_type": "code",
   "execution_count": 1,
   "id": "5b207b23",
   "metadata": {},
   "outputs": [],
   "source": [
    "import torch\n",
    "import torch.nn as nn\n",
    "import numpy as np\n",
    "import matplotlib.pyplot as plt\n",
    "import scipy.io"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "id": "7d15c703",
   "metadata": {},
   "outputs": [],
   "source": [
    "# Define the LSTM model\n",
    "class LSTM(nn.Module):\n",
    "    def __init__(self, input_size, hidden_size, output_size):\n",
    "        super(LSTM, self).__init__()\n",
    "\n",
    "        self.hidden_size = hidden_size\n",
    "\n",
    "        self.lstm = nn.LSTM(input_size, hidden_size, batch_first=True)\n",
    "        self.fc = nn.Linear(hidden_size, output_size)\n",
    "\n",
    "    def forward(self, x, hidden):\n",
    "        output, hidden = self.lstm(x, hidden)\n",
    "        output = self.fc(output)\n",
    "        return output, hidden\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "id": "5fcd1e58",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "x size (1, 256)\n",
      "t size (1, 100)\n",
      "u size (256, 100)\n"
     ]
    },
    {
     "data": {
      "image/png": "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\n",
      "text/plain": [
       "<Figure size 1080x360 with 2 Axes>"
      ]
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "# importing data\n",
    "\n",
    "# Load the .mat file\n",
    "mat_data = scipy.io.loadmat('burg.mat')\n",
    "\n",
    "# Access the variables stored in the .mat file\n",
    "# The variable names in the .mat file become keys in the loaded dictionary\n",
    "x = mat_data['x']\n",
    "t = mat_data['t']\n",
    "u = mat_data['u1']\n",
    "\n",
    "#Use the loaded variables as needed\n",
    "print(\"x size\", x.shape)\n",
    "print(\"t size\", t.shape)\n",
    "print(\"u size\", u.shape)\n",
    "\n",
    "X, T = np.meshgrid(x, t)\n",
    "# Define custom color levels\n",
    "c_levels = np.linspace(np.min(u), np.max(u), 100)\n",
    "\n",
    "# Plot the contour\n",
    "plt.figure(figsize=(15, 5))\n",
    "plt.contourf(T, X, u.T, levels=c_levels, cmap='coolwarm')\n",
    "plt.xlabel('t')\n",
    "plt.ylabel('x')\n",
    "plt.title('Burgers')\n",
    "plt.colorbar()  # Add a colorbar for the contour levels\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "id": "ed198870",
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "(256, 100)"
      ]
     },
     "execution_count": 4,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "# Set random seed for reproducibility\n",
    "torch.manual_seed(42)\n",
    "\n",
    "# Toy problem data\n",
    "input_size = 256\n",
    "hidden_size = 32\n",
    "output_size = 256\n",
    "sequence_length = 79\n",
    "batch_size = 1\n",
    "num_epochs = 20000\n",
    "\n",
    "# Set random seed for reproducibility\n",
    "torch.manual_seed(42)\n",
    "u[:, 0:100].shape"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "id": "070468a7",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "test data shape (256,)\n",
      "test target shape (256, 20)\n",
      "input data shape (256, 79)\n",
      "Target data shape (256, 79)\n",
      "input tensor shape torch.Size([1, 79, 256])\n",
      "Target tensor shape torch.Size([1, 79, 256])\n"
     ]
    }
   ],
   "source": [
    "input_data = u[:,0:79]\n",
    "target_data = u[:,1:80]\n",
    "\n",
    "test_data = u[:,79]\n",
    "test_target = u[:,80:100]\n",
    "\n",
    "print(\"test data shape\", test_data.shape)\n",
    "print(\"test target shape\", test_target.shape)\n",
    "\n",
    "print(\"input data shape\",input_data.shape)\n",
    "print(\"Target data shape\",target_data.shape)\n",
    "\n",
    "# Convert data to tensors\n",
    "input_tensor = torch.tensor(input_data.T).view(batch_size, sequence_length, input_size).float()\n",
    "target_tensor = torch.tensor(target_data.T).view(batch_size, sequence_length, output_size).float()\n",
    "\n",
    "print(\"input tensor shape\",input_tensor.shape)\n",
    "print(\"Target tensor shape\",target_tensor.shape)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 6,
   "id": "003fce5f",
   "metadata": {},
   "outputs": [],
   "source": [
    "# Convert test data to tensors\n",
    "test_tensor = torch.tensor(test_data.T).view(batch_size, 1, input_size).float()\n",
    "test_target_tensor = torch.tensor(test_target.T).view(batch_size, 20, output_size).float()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "56bc9fad",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Epoch: 10/20000, Loss: 0.04868699\n",
      "Epoch: 20/20000, Loss: 0.03755799\n",
      "Epoch: 30/20000, Loss: 0.02935270\n",
      "Epoch: 40/20000, Loss: 0.02656572\n",
      "Epoch: 50/20000, Loss: 0.02571796\n",
      "Epoch: 60/20000, Loss: 0.02496230\n",
      "Epoch: 70/20000, Loss: 0.02262440\n",
      "Epoch: 80/20000, Loss: 0.02028687\n",
      "Epoch: 90/20000, Loss: 0.01620742\n",
      "Epoch: 100/20000, Loss: 0.00933764\n",
      "Epoch: 110/20000, Loss: 0.00531531\n",
      "Epoch: 120/20000, Loss: 0.00384806\n",
      "Epoch: 130/20000, Loss: 0.00328149\n",
      "Epoch: 140/20000, Loss: 0.00290461\n",
      "Epoch: 150/20000, Loss: 0.00274521\n",
      "Epoch: 160/20000, Loss: 0.00249488\n",
      "Epoch: 170/20000, Loss: 0.00232613\n",
      "Epoch: 180/20000, Loss: 0.00219083\n",
      "Epoch: 190/20000, Loss: 0.00207542\n",
      "Epoch: 200/20000, Loss: 0.00197175\n",
      "Epoch: 210/20000, Loss: 0.00187902\n",
      "Epoch: 220/20000, Loss: 0.00179559\n",
      "Epoch: 230/20000, Loss: 0.00172027\n",
      "Epoch: 240/20000, Loss: 0.00165198\n",
      "Epoch: 250/20000, Loss: 0.00158895\n",
      "Epoch: 260/20000, Loss: 0.00158098\n",
      "Epoch: 270/20000, Loss: 0.00149214\n",
      "Epoch: 280/20000, Loss: 0.00145146\n",
      "Epoch: 290/20000, Loss: 0.00140868\n",
      "Epoch: 300/20000, Loss: 0.00136926\n",
      "Epoch: 310/20000, Loss: 0.00133440\n",
      "Epoch: 320/20000, Loss: 0.00130710\n",
      "Epoch: 330/20000, Loss: 0.00131877\n",
      "Epoch: 340/20000, Loss: 0.00126761\n",
      "Epoch: 350/20000, Loss: 0.00122971\n",
      "Epoch: 360/20000, Loss: 0.00120512\n",
      "Epoch: 370/20000, Loss: 0.00118419\n",
      "Epoch: 380/20000, Loss: 0.00116449\n",
      "Epoch: 390/20000, Loss: 0.00114671\n",
      "Epoch: 400/20000, Loss: 0.00116551\n",
      "Epoch: 410/20000, Loss: 0.00114328\n",
      "Epoch: 420/20000, Loss: 0.00110884\n",
      "Epoch: 430/20000, Loss: 0.00108640\n",
      "Epoch: 440/20000, Loss: 0.00107380\n",
      "Epoch: 450/20000, Loss: 0.00106043\n",
      "Epoch: 460/20000, Loss: 0.00105472\n",
      "Epoch: 470/20000, Loss: 0.00104527\n",
      "Epoch: 480/20000, Loss: 0.00102682\n",
      "Epoch: 490/20000, Loss: 0.00102039\n",
      "Epoch: 500/20000, Loss: 0.00100858\n",
      "Epoch: 510/20000, Loss: 0.00099591\n",
      "Epoch: 520/20000, Loss: 0.00099681\n",
      "Epoch: 530/20000, Loss: 0.00097950\n",
      "Epoch: 540/20000, Loss: 0.00098913\n",
      "Epoch: 550/20000, Loss: 0.00096035\n",
      "Epoch: 560/20000, Loss: 0.00095450\n",
      "Epoch: 570/20000, Loss: 0.00094496\n",
      "Epoch: 580/20000, Loss: 0.00093630\n",
      "Epoch: 590/20000, Loss: 0.00093491\n",
      "Epoch: 600/20000, Loss: 0.00092304\n",
      "Epoch: 610/20000, Loss: 0.00094065\n",
      "Epoch: 620/20000, Loss: 0.00091539\n",
      "Epoch: 630/20000, Loss: 0.00090057\n",
      "Epoch: 640/20000, Loss: 0.00089471\n",
      "Epoch: 650/20000, Loss: 0.00088771\n",
      "Epoch: 660/20000, Loss: 0.00088198\n",
      "Epoch: 670/20000, Loss: 0.00089583\n",
      "Epoch: 680/20000, Loss: 0.00087299\n",
      "Epoch: 690/20000, Loss: 0.00089674\n",
      "Epoch: 700/20000, Loss: 0.00086017\n",
      "Epoch: 710/20000, Loss: 0.00085902\n",
      "Epoch: 720/20000, Loss: 0.00085167\n",
      "Epoch: 730/20000, Loss: 0.00084424\n",
      "Epoch: 740/20000, Loss: 0.00084104\n",
      "Epoch: 750/20000, Loss: 0.00108884\n",
      "Epoch: 760/20000, Loss: 0.00085308\n",
      "Epoch: 770/20000, Loss: 0.00084897\n",
      "Epoch: 780/20000, Loss: 0.00083458\n",
      "Epoch: 790/20000, Loss: 0.00082335\n",
      "Epoch: 800/20000, Loss: 0.00081613\n",
      "Epoch: 810/20000, Loss: 0.00081306\n",
      "Epoch: 820/20000, Loss: 0.00080886\n",
      "Epoch: 830/20000, Loss: 0.00080519\n",
      "Epoch: 840/20000, Loss: 0.00080153\n",
      "Epoch: 850/20000, Loss: 0.00079943\n",
      "Epoch: 860/20000, Loss: 0.00111349\n",
      "Epoch: 870/20000, Loss: 0.00083163\n",
      "Epoch: 880/20000, Loss: 0.00082841\n",
      "Epoch: 890/20000, Loss: 0.00079662\n",
      "Epoch: 900/20000, Loss: 0.00078674\n",
      "Epoch: 910/20000, Loss: 0.00078318\n",
      "Epoch: 920/20000, Loss: 0.00077929\n",
      "Epoch: 930/20000, Loss: 0.00077609\n",
      "Epoch: 940/20000, Loss: 0.00077319\n",
      "Epoch: 950/20000, Loss: 0.00077053\n",
      "Epoch: 960/20000, Loss: 0.00076794\n",
      "Epoch: 970/20000, Loss: 0.00076673\n",
      "Epoch: 980/20000, Loss: 0.00097210\n",
      "Epoch: 990/20000, Loss: 0.00080499\n",
      "Epoch: 1000/20000, Loss: 0.00078551\n",
      "Epoch: 1010/20000, Loss: 0.00076748\n",
      "Epoch: 1020/20000, Loss: 0.00075754\n",
      "Epoch: 1030/20000, Loss: 0.00075384\n",
      "Epoch: 1040/20000, Loss: 0.00075110\n",
      "Epoch: 1050/20000, Loss: 0.00074847\n",
      "Epoch: 1060/20000, Loss: 0.00074627\n",
      "Epoch: 1070/20000, Loss: 0.00075101\n",
      "Epoch: 1080/20000, Loss: 0.00078482\n",
      "Epoch: 1090/20000, Loss: 0.00074428\n",
      "Epoch: 1100/20000, Loss: 0.00075932\n",
      "Epoch: 1110/20000, Loss: 0.00074624\n",
      "Epoch: 1120/20000, Loss: 0.00073838\n",
      "Epoch: 1130/20000, Loss: 0.00073545\n",
      "Epoch: 1140/20000, Loss: 0.00073324\n",
      "Epoch: 1150/20000, Loss: 0.00073279\n",
      "Epoch: 1160/20000, Loss: 0.00077026\n",
      "Epoch: 1170/20000, Loss: 0.00074350\n",
      "Epoch: 1180/20000, Loss: 0.00072944\n",
      "Epoch: 1190/20000, Loss: 0.00072561\n",
      "Epoch: 1200/20000, Loss: 0.00078790\n",
      "Epoch: 1210/20000, Loss: 0.00078839\n",
      "Epoch: 1220/20000, Loss: 0.00072089\n",
      "Epoch: 1230/20000, Loss: 0.00072426\n",
      "Epoch: 1240/20000, Loss: 0.00072042\n",
      "Epoch: 1250/20000, Loss: 0.00077737\n",
      "Epoch: 1260/20000, Loss: 0.00074742\n",
      "Epoch: 1270/20000, Loss: 0.00072900\n",
      "Epoch: 1280/20000, Loss: 0.00071912\n",
      "Epoch: 1290/20000, Loss: 0.00075268\n",
      "Epoch: 1300/20000, Loss: 0.00071612\n",
      "Epoch: 1310/20000, Loss: 0.00072943\n",
      "Epoch: 1320/20000, Loss: 0.00070970\n",
      "Epoch: 1330/20000, Loss: 0.00070705\n",
      "Epoch: 1340/20000, Loss: 0.00070508\n",
      "Epoch: 1350/20000, Loss: 0.00070458\n",
      "Epoch: 1360/20000, Loss: 0.00071084\n",
      "Epoch: 1370/20000, Loss: 0.00084533\n",
      "Epoch: 1380/20000, Loss: 0.00073912\n",
      "Epoch: 1390/20000, Loss: 0.00070488\n",
      "Epoch: 1400/20000, Loss: 0.00070210\n",
      "Epoch: 1410/20000, Loss: 0.00069923\n",
      "Epoch: 1420/20000, Loss: 0.00069581\n",
      "Epoch: 1430/20000, Loss: 0.00069503\n",
      "Epoch: 1440/20000, Loss: 0.00071388\n",
      "Epoch: 1450/20000, Loss: 0.00073927\n",
      "Epoch: 1460/20000, Loss: 0.00072598\n",
      "Epoch: 1470/20000, Loss: 0.00070014\n",
      "Epoch: 1480/20000, Loss: 0.00069185\n",
      "Epoch: 1490/20000, Loss: 0.00069094\n",
      "Epoch: 1500/20000, Loss: 0.00068875\n",
      "Epoch: 1510/20000, Loss: 0.00068673\n",
      "Epoch: 1520/20000, Loss: 0.00068608\n",
      "Epoch: 1530/20000, Loss: 0.00069062\n",
      "Epoch: 1540/20000, Loss: 0.00088732\n",
      "Epoch: 1550/20000, Loss: 0.00074404\n",
      "Epoch: 1560/20000, Loss: 0.00069194\n",
      "Epoch: 1570/20000, Loss: 0.00068638\n",
      "Epoch: 1580/20000, Loss: 0.00068080\n",
      "Epoch: 1590/20000, Loss: 0.00068033\n",
      "Epoch: 1600/20000, Loss: 0.00067848\n",
      "Epoch: 1610/20000, Loss: 0.00067714\n",
      "Epoch: 1620/20000, Loss: 0.00067635\n",
      "Epoch: 1630/20000, Loss: 0.00067791\n",
      "Epoch: 1640/20000, Loss: 0.00079785\n",
      "Epoch: 1650/20000, Loss: 0.00073008\n",
      "Epoch: 1660/20000, Loss: 0.00069412\n",
      "Epoch: 1670/20000, Loss: 0.00067396\n",
      "Epoch: 1680/20000, Loss: 0.00067520\n",
      "Epoch: 1690/20000, Loss: 0.00067029\n",
      "Epoch: 1700/20000, Loss: 0.00066963\n",
      "Epoch: 1710/20000, Loss: 0.00066859\n",
      "Epoch: 1720/20000, Loss: 0.00066763\n",
      "Epoch: 1730/20000, Loss: 0.00066811\n",
      "Epoch: 1740/20000, Loss: 0.00077329\n",
      "Epoch: 1750/20000, Loss: 0.00073536\n",
      "Epoch: 1760/20000, Loss: 0.00069169\n",
      "Epoch: 1770/20000, Loss: 0.00066410\n",
      "Epoch: 1780/20000, Loss: 0.00066725\n",
      "Epoch: 1790/20000, Loss: 0.00066236\n",
      "Epoch: 1800/20000, Loss: 0.00066180\n",
      "Epoch: 1810/20000, Loss: 0.00066054\n",
      "Epoch: 1820/20000, Loss: 0.00065945\n",
      "Epoch: 1830/20000, Loss: 0.00065863\n",
      "Epoch: 1840/20000, Loss: 0.00065799\n",
      "Epoch: 1850/20000, Loss: 0.00066638\n",
      "Epoch: 1860/20000, Loss: 0.00092536\n",
      "Epoch: 1870/20000, Loss: 0.00066416\n",
      "Epoch: 1880/20000, Loss: 0.00067457\n",
      "Epoch: 1890/20000, Loss: 0.00066019\n",
      "Epoch: 1900/20000, Loss: 0.00065527\n",
      "Epoch: 1910/20000, Loss: 0.00065349\n",
      "Epoch: 1920/20000, Loss: 0.00065242\n",
      "Epoch: 1930/20000, Loss: 0.00065120\n",
      "Epoch: 1940/20000, Loss: 0.00065032\n",
      "Epoch: 1950/20000, Loss: 0.00064948\n",
      "Epoch: 1960/20000, Loss: 0.00064872\n",
      "Epoch: 1970/20000, Loss: 0.00064814\n",
      "Epoch: 1980/20000, Loss: 0.00065833\n",
      "Epoch: 1990/20000, Loss: 0.00085451\n",
      "Epoch: 2000/20000, Loss: 0.00070635\n",
      "Epoch: 2010/20000, Loss: 0.00065174\n",
      "Epoch: 2020/20000, Loss: 0.00064653\n",
      "Epoch: 2030/20000, Loss: 0.00064767\n",
      "Epoch: 2040/20000, Loss: 0.00064285\n",
      "Epoch: 2050/20000, Loss: 0.00065799\n",
      "Epoch: 2060/20000, Loss: 0.00064306\n",
      "Epoch: 2070/20000, Loss: 0.00065671\n",
      "Epoch: 2080/20000, Loss: 0.00064325\n",
      "Epoch: 2090/20000, Loss: 0.00065436\n",
      "Epoch: 2100/20000, Loss: 0.00066055\n",
      "Epoch: 2110/20000, Loss: 0.00065058\n",
      "Epoch: 2120/20000, Loss: 0.00064921\n",
      "Epoch: 2130/20000, Loss: 0.00065513\n",
      "Epoch: 2140/20000, Loss: 0.00068292\n",
      "Epoch: 2150/20000, Loss: 0.00064266\n",
      "Epoch: 2160/20000, Loss: 0.00063739\n",
      "Epoch: 2170/20000, Loss: 0.00065930\n",
      "Epoch: 2180/20000, Loss: 0.00065150\n",
      "Epoch: 2190/20000, Loss: 0.00063274\n",
      "Epoch: 2200/20000, Loss: 0.00066329\n",
      "Epoch: 2210/20000, Loss: 0.00071427\n",
      "Epoch: 2220/20000, Loss: 0.00064713\n",
      "Epoch: 2230/20000, Loss: 0.00063726\n",
      "Epoch: 2240/20000, Loss: 0.00062922\n",
      "Epoch: 2250/20000, Loss: 0.00066190\n",
      "Epoch: 2260/20000, Loss: 0.00063746\n",
      "Epoch: 2270/20000, Loss: 0.00063020\n",
      "Epoch: 2280/20000, Loss: 0.00064833\n",
      "Epoch: 2290/20000, Loss: 0.00068032\n",
      "Epoch: 2300/20000, Loss: 0.00063434\n",
      "Epoch: 2310/20000, Loss: 0.00062480\n",
      "Epoch: 2320/20000, Loss: 0.00064742\n"
     ]
    },
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Epoch: 2330/20000, Loss: 0.00065093\n",
      "Epoch: 2340/20000, Loss: 0.00063173\n",
      "Epoch: 2350/20000, Loss: 0.00062211\n",
      "Epoch: 2360/20000, Loss: 0.00064989\n",
      "Epoch: 2370/20000, Loss: 0.00066121\n",
      "Epoch: 2380/20000, Loss: 0.00063143\n",
      "Epoch: 2390/20000, Loss: 0.00062030\n",
      "Epoch: 2400/20000, Loss: 0.00063489\n",
      "Epoch: 2410/20000, Loss: 0.00062373\n",
      "Epoch: 2420/20000, Loss: 0.00070585\n",
      "Epoch: 2430/20000, Loss: 0.00063013\n",
      "Epoch: 2440/20000, Loss: 0.00063485\n",
      "Epoch: 2450/20000, Loss: 0.00062746\n",
      "Epoch: 2460/20000, Loss: 0.00062085\n",
      "Epoch: 2470/20000, Loss: 0.00062536\n",
      "Epoch: 2480/20000, Loss: 0.00062470\n",
      "Epoch: 2490/20000, Loss: 0.00062841\n",
      "Epoch: 2500/20000, Loss: 0.00063850\n",
      "Epoch: 2510/20000, Loss: 0.00062000\n",
      "Epoch: 2520/20000, Loss: 0.00061897\n",
      "Epoch: 2530/20000, Loss: 0.00062245\n",
      "Epoch: 2540/20000, Loss: 0.00063501\n",
      "Epoch: 2550/20000, Loss: 0.00067648\n",
      "Epoch: 2560/20000, Loss: 0.00062736\n",
      "Epoch: 2570/20000, Loss: 0.00061816\n",
      "Epoch: 2580/20000, Loss: 0.00063051\n",
      "Epoch: 2590/20000, Loss: 0.00061267\n",
      "Epoch: 2600/20000, Loss: 0.00060954\n",
      "Epoch: 2610/20000, Loss: 0.00062343\n",
      "Epoch: 2620/20000, Loss: 0.00062864\n",
      "Epoch: 2630/20000, Loss: 0.00060841\n",
      "Epoch: 2640/20000, Loss: 0.00060720\n",
      "Epoch: 2650/20000, Loss: 0.00062029\n",
      "Epoch: 2660/20000, Loss: 0.00062062\n",
      "Epoch: 2670/20000, Loss: 0.00076493\n",
      "Epoch: 2680/20000, Loss: 0.00062624\n",
      "Epoch: 2690/20000, Loss: 0.00062178\n",
      "Epoch: 2700/20000, Loss: 0.00062346\n",
      "Epoch: 2710/20000, Loss: 0.00060471\n",
      "Epoch: 2720/20000, Loss: 0.00060647\n",
      "Epoch: 2730/20000, Loss: 0.00061316\n",
      "Epoch: 2740/20000, Loss: 0.00060616\n",
      "Epoch: 2750/20000, Loss: 0.00060539\n",
      "Epoch: 2760/20000, Loss: 0.00062129\n",
      "Epoch: 2770/20000, Loss: 0.00064950\n",
      "Epoch: 2780/20000, Loss: 0.00060055\n",
      "Epoch: 2790/20000, Loss: 0.00059892\n",
      "Epoch: 2800/20000, Loss: 0.00061551\n",
      "Epoch: 2810/20000, Loss: 0.00061979\n",
      "Epoch: 2820/20000, Loss: 0.00067674\n",
      "Epoch: 2830/20000, Loss: 0.00061233\n",
      "Epoch: 2840/20000, Loss: 0.00059554\n",
      "Epoch: 2850/20000, Loss: 0.00061750\n",
      "Epoch: 2860/20000, Loss: 0.00059365\n",
      "Epoch: 2870/20000, Loss: 0.00059320\n",
      "Epoch: 2880/20000, Loss: 0.00058960\n",
      "Epoch: 2890/20000, Loss: 0.00074227\n",
      "Epoch: 2900/20000, Loss: 0.00076386\n",
      "Epoch: 2910/20000, Loss: 0.00064968\n",
      "Epoch: 2920/20000, Loss: 0.00059949\n",
      "Epoch: 2930/20000, Loss: 0.00058408\n",
      "Epoch: 2940/20000, Loss: 0.00057208\n",
      "Epoch: 2950/20000, Loss: 0.00056460\n",
      "Epoch: 2960/20000, Loss: 0.00058875\n",
      "Epoch: 2970/20000, Loss: 0.00056623\n",
      "Epoch: 2980/20000, Loss: 0.00056455\n",
      "Epoch: 2990/20000, Loss: 0.00058976\n",
      "Epoch: 3000/20000, Loss: 0.00052533\n",
      "Epoch: 3010/20000, Loss: 0.00051866\n",
      "Epoch: 3020/20000, Loss: 0.00062079\n",
      "Epoch: 3030/20000, Loss: 0.00049490\n",
      "Epoch: 3040/20000, Loss: 0.00048913\n",
      "Epoch: 3050/20000, Loss: 0.00046731\n",
      "Epoch: 3060/20000, Loss: 0.00054503\n",
      "Epoch: 3070/20000, Loss: 0.00044238\n",
      "Epoch: 3080/20000, Loss: 0.00041563\n",
      "Epoch: 3090/20000, Loss: 0.00043675\n",
      "Epoch: 3100/20000, Loss: 0.00042492\n",
      "Epoch: 3110/20000, Loss: 0.00037431\n",
      "Epoch: 3120/20000, Loss: 0.00036120\n",
      "Epoch: 3130/20000, Loss: 0.00094155\n",
      "Epoch: 3140/20000, Loss: 0.00037248\n",
      "Epoch: 3150/20000, Loss: 0.00043611\n",
      "Epoch: 3160/20000, Loss: 0.00032912\n",
      "Epoch: 3170/20000, Loss: 0.00032740\n",
      "Epoch: 3180/20000, Loss: 0.00031155\n",
      "Epoch: 3190/20000, Loss: 0.00029809\n",
      "Epoch: 3200/20000, Loss: 0.00028628\n",
      "Epoch: 3210/20000, Loss: 0.00027622\n",
      "Epoch: 3220/20000, Loss: 0.00026744\n",
      "Epoch: 3230/20000, Loss: 0.00025913\n",
      "Epoch: 3240/20000, Loss: 0.00025140\n",
      "Epoch: 3250/20000, Loss: 0.00024424\n",
      "Epoch: 3260/20000, Loss: 0.00024964\n",
      "Epoch: 3270/20000, Loss: 0.00043311\n",
      "Epoch: 3280/20000, Loss: 0.00037456\n",
      "Epoch: 3290/20000, Loss: 0.00027472\n",
      "Epoch: 3300/20000, Loss: 0.00023778\n",
      "Epoch: 3310/20000, Loss: 0.00022410\n",
      "Epoch: 3320/20000, Loss: 0.00021320\n",
      "Epoch: 3330/20000, Loss: 0.00020618\n",
      "Epoch: 3340/20000, Loss: 0.00019622\n",
      "Epoch: 3350/20000, Loss: 0.00018899\n",
      "Epoch: 3360/20000, Loss: 0.00018022\n",
      "Epoch: 3370/20000, Loss: 0.00017096\n",
      "Epoch: 3380/20000, Loss: 0.00016117\n",
      "Epoch: 3390/20000, Loss: 0.00015099\n",
      "Epoch: 3400/20000, Loss: 0.00014436\n",
      "Epoch: 3410/20000, Loss: 0.00045368\n",
      "Epoch: 3420/20000, Loss: 0.00017790\n",
      "Epoch: 3430/20000, Loss: 0.00014977\n",
      "Epoch: 3440/20000, Loss: 0.00011567\n",
      "Epoch: 3450/20000, Loss: 0.00010076\n",
      "Epoch: 3460/20000, Loss: 0.00009736\n",
      "Epoch: 3470/20000, Loss: 0.00009186\n",
      "Epoch: 3480/20000, Loss: 0.00008894\n",
      "Epoch: 3490/20000, Loss: 0.00008630\n",
      "Epoch: 3500/20000, Loss: 0.00008434\n",
      "Epoch: 3510/20000, Loss: 0.00008273\n",
      "Epoch: 3520/20000, Loss: 0.00008136\n",
      "Epoch: 3530/20000, Loss: 0.00008019\n",
      "Epoch: 3540/20000, Loss: 0.00007915\n",
      "Epoch: 3550/20000, Loss: 0.00007822\n",
      "Epoch: 3560/20000, Loss: 0.00007742\n",
      "Epoch: 3570/20000, Loss: 0.00007990\n",
      "Epoch: 3580/20000, Loss: 0.00011418\n",
      "Epoch: 3590/20000, Loss: 0.00013107\n",
      "Epoch: 3600/20000, Loss: 0.00009445\n",
      "Epoch: 3610/20000, Loss: 0.00008048\n",
      "Epoch: 3620/20000, Loss: 0.00007328\n",
      "Epoch: 3630/20000, Loss: 0.00007493\n",
      "Epoch: 3640/20000, Loss: 0.00007341\n",
      "Epoch: 3650/20000, Loss: 0.00007625\n",
      "Epoch: 3660/20000, Loss: 0.00013809\n",
      "Epoch: 3670/20000, Loss: 0.00009762\n",
      "Epoch: 3680/20000, Loss: 0.00007064\n",
      "Epoch: 3690/20000, Loss: 0.00007295\n",
      "Epoch: 3700/20000, Loss: 0.00007119\n",
      "Epoch: 3710/20000, Loss: 0.00006880\n",
      "Epoch: 3720/20000, Loss: 0.00006798\n",
      "Epoch: 3730/20000, Loss: 0.00006760\n",
      "Epoch: 3740/20000, Loss: 0.00006682\n",
      "Epoch: 3750/20000, Loss: 0.00006623\n",
      "Epoch: 3760/20000, Loss: 0.00006587\n",
      "Epoch: 3770/20000, Loss: 0.00007266\n",
      "Epoch: 3780/20000, Loss: 0.00040997\n",
      "Epoch: 3790/20000, Loss: 0.00017908\n",
      "Epoch: 3800/20000, Loss: 0.00010630\n",
      "Epoch: 3810/20000, Loss: 0.00007395\n",
      "Epoch: 3820/20000, Loss: 0.00006501\n",
      "Epoch: 3830/20000, Loss: 0.00006347\n",
      "Epoch: 3840/20000, Loss: 0.00006289\n",
      "Epoch: 3850/20000, Loss: 0.00006189\n",
      "Epoch: 3860/20000, Loss: 0.00006146\n",
      "Epoch: 3870/20000, Loss: 0.00006095\n",
      "Epoch: 3880/20000, Loss: 0.00006052\n",
      "Epoch: 3890/20000, Loss: 0.00006011\n",
      "Epoch: 3900/20000, Loss: 0.00006006\n",
      "Epoch: 3910/20000, Loss: 0.00005992\n",
      "Epoch: 3920/20000, Loss: 0.00005893\n",
      "Epoch: 3930/20000, Loss: 0.00005851\n",
      "Epoch: 3940/20000, Loss: 0.00005810\n",
      "Epoch: 3950/20000, Loss: 0.00005770\n",
      "Epoch: 3960/20000, Loss: 0.00005756\n",
      "Epoch: 3970/20000, Loss: 0.00007851\n",
      "Epoch: 3980/20000, Loss: 0.00038380\n",
      "Epoch: 3990/20000, Loss: 0.00017708\n",
      "Epoch: 4000/20000, Loss: 0.00008872\n",
      "Epoch: 4010/20000, Loss: 0.00006227\n",
      "Epoch: 4020/20000, Loss: 0.00005760\n",
      "Epoch: 4030/20000, Loss: 0.00005600\n",
      "Epoch: 4040/20000, Loss: 0.00005496\n",
      "Epoch: 4050/20000, Loss: 0.00005462\n",
      "Epoch: 4060/20000, Loss: 0.00005404\n",
      "Epoch: 4070/20000, Loss: 0.00005362\n",
      "Epoch: 4080/20000, Loss: 0.00005365\n",
      "Epoch: 4090/20000, Loss: 0.00005310\n",
      "Epoch: 4100/20000, Loss: 0.00005256\n",
      "Epoch: 4110/20000, Loss: 0.00005224\n",
      "Epoch: 4120/20000, Loss: 0.00005188\n",
      "Epoch: 4130/20000, Loss: 0.00005155\n",
      "Epoch: 4140/20000, Loss: 0.00005126\n",
      "Epoch: 4150/20000, Loss: 0.00005415\n",
      "Epoch: 4160/20000, Loss: 0.00036380\n",
      "Epoch: 4170/20000, Loss: 0.00018137\n",
      "Epoch: 4180/20000, Loss: 0.00010405\n",
      "Epoch: 4190/20000, Loss: 0.00006893\n",
      "Epoch: 4200/20000, Loss: 0.00005354\n",
      "Epoch: 4210/20000, Loss: 0.00004933\n",
      "Epoch: 4220/20000, Loss: 0.00004957\n",
      "Epoch: 4230/20000, Loss: 0.00004871\n",
      "Epoch: 4240/20000, Loss: 0.00004822\n",
      "Epoch: 4250/20000, Loss: 0.00004795\n",
      "Epoch: 4260/20000, Loss: 0.00004851\n",
      "Epoch: 4270/20000, Loss: 0.00008929\n",
      "Epoch: 4280/20000, Loss: 0.00005205\n",
      "Epoch: 4290/20000, Loss: 0.00005192\n",
      "Epoch: 4300/20000, Loss: 0.00005005\n",
      "Epoch: 4310/20000, Loss: 0.00004801\n",
      "Epoch: 4320/20000, Loss: 0.00004645\n",
      "Epoch: 4330/20000, Loss: 0.00004570\n",
      "Epoch: 4340/20000, Loss: 0.00004557\n",
      "Epoch: 4350/20000, Loss: 0.00004510\n",
      "Epoch: 4360/20000, Loss: 0.00004480\n",
      "Epoch: 4370/20000, Loss: 0.00004475\n",
      "Epoch: 4380/20000, Loss: 0.00005903\n",
      "Epoch: 4390/20000, Loss: 0.00025663\n",
      "Epoch: 4400/20000, Loss: 0.00006249\n",
      "Epoch: 4410/20000, Loss: 0.00006467\n",
      "Epoch: 4420/20000, Loss: 0.00005399\n",
      "Epoch: 4430/20000, Loss: 0.00004529\n",
      "Epoch: 4440/20000, Loss: 0.00004404\n",
      "Epoch: 4450/20000, Loss: 0.00004283\n",
      "Epoch: 4460/20000, Loss: 0.00004243\n",
      "Epoch: 4470/20000, Loss: 0.00004217\n",
      "Epoch: 4480/20000, Loss: 0.00004172\n",
      "Epoch: 4490/20000, Loss: 0.00004146\n",
      "Epoch: 4500/20000, Loss: 0.00004128\n",
      "Epoch: 4510/20000, Loss: 0.00004860\n",
      "Epoch: 4520/20000, Loss: 0.00047239\n",
      "Epoch: 4530/20000, Loss: 0.00004356\n",
      "Epoch: 4540/20000, Loss: 0.00004664\n",
      "Epoch: 4550/20000, Loss: 0.00004661\n",
      "Epoch: 4560/20000, Loss: 0.00004556\n",
      "Epoch: 4570/20000, Loss: 0.00004066\n",
      "Epoch: 4580/20000, Loss: 0.00003994\n",
      "Epoch: 4590/20000, Loss: 0.00004124\n",
      "Epoch: 4600/20000, Loss: 0.00007412\n"
     ]
    },
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Epoch: 4610/20000, Loss: 0.00004125\n",
      "Epoch: 4620/20000, Loss: 0.00004417\n",
      "Epoch: 4630/20000, Loss: 0.00004274\n",
      "Epoch: 4640/20000, Loss: 0.00003978\n",
      "Epoch: 4650/20000, Loss: 0.00003805\n",
      "Epoch: 4660/20000, Loss: 0.00003769\n",
      "Epoch: 4670/20000, Loss: 0.00003922\n",
      "Epoch: 4680/20000, Loss: 0.00007163\n",
      "Epoch: 4690/20000, Loss: 0.00007830\n",
      "Epoch: 4700/20000, Loss: 0.00004644\n",
      "Epoch: 4710/20000, Loss: 0.00003840\n",
      "Epoch: 4720/20000, Loss: 0.00003710\n",
      "Epoch: 4730/20000, Loss: 0.00003699\n",
      "Epoch: 4740/20000, Loss: 0.00003665\n",
      "Epoch: 4750/20000, Loss: 0.00003577\n",
      "Epoch: 4760/20000, Loss: 0.00003584\n",
      "Epoch: 4770/20000, Loss: 0.00004320\n",
      "Epoch: 4780/20000, Loss: 0.00015288\n",
      "Epoch: 4790/20000, Loss: 0.00010073\n",
      "Epoch: 4800/20000, Loss: 0.00012265\n",
      "Epoch: 4810/20000, Loss: 0.00005449\n",
      "Epoch: 4820/20000, Loss: 0.00003669\n",
      "Epoch: 4830/20000, Loss: 0.00003439\n",
      "Epoch: 4840/20000, Loss: 0.00003403\n",
      "Epoch: 4850/20000, Loss: 0.00003405\n",
      "Epoch: 4860/20000, Loss: 0.00003373\n",
      "Epoch: 4870/20000, Loss: 0.00003338\n",
      "Epoch: 4880/20000, Loss: 0.00004039\n",
      "Epoch: 4890/20000, Loss: 0.00029921\n",
      "Epoch: 4900/20000, Loss: 0.00011963\n",
      "Epoch: 4910/20000, Loss: 0.00004839\n",
      "Epoch: 4920/20000, Loss: 0.00004137\n",
      "Epoch: 4930/20000, Loss: 0.00003361\n",
      "Epoch: 4940/20000, Loss: 0.00003404\n",
      "Epoch: 4950/20000, Loss: 0.00003262\n",
      "Epoch: 4960/20000, Loss: 0.00003196\n",
      "Epoch: 4970/20000, Loss: 0.00003231\n",
      "Epoch: 4980/20000, Loss: 0.00005212\n",
      "Epoch: 4990/20000, Loss: 0.00012242\n",
      "Epoch: 5000/20000, Loss: 0.00005178\n",
      "Epoch: 5010/20000, Loss: 0.00003246\n",
      "Epoch: 5020/20000, Loss: 0.00003147\n",
      "Epoch: 5030/20000, Loss: 0.00003112\n",
      "Epoch: 5040/20000, Loss: 0.00003121\n",
      "Epoch: 5050/20000, Loss: 0.00003160\n",
      "Epoch: 5060/20000, Loss: 0.00007074\n",
      "Epoch: 5070/20000, Loss: 0.00008393\n",
      "Epoch: 5080/20000, Loss: 0.00004715\n",
      "Epoch: 5090/20000, Loss: 0.00003765\n",
      "Epoch: 5100/20000, Loss: 0.00003195\n",
      "Epoch: 5110/20000, Loss: 0.00003356\n",
      "Epoch: 5120/20000, Loss: 0.00005081\n",
      "Epoch: 5130/20000, Loss: 0.00005372\n",
      "Epoch: 5140/20000, Loss: 0.00003852\n",
      "Epoch: 5150/20000, Loss: 0.00002926\n",
      "Epoch: 5160/20000, Loss: 0.00003139\n",
      "Epoch: 5170/20000, Loss: 0.00004136\n",
      "Epoch: 5180/20000, Loss: 0.00006354\n",
      "Epoch: 5190/20000, Loss: 0.00002843\n",
      "Epoch: 5200/20000, Loss: 0.00003804\n",
      "Epoch: 5210/20000, Loss: 0.00006457\n",
      "Epoch: 5220/20000, Loss: 0.00010750\n",
      "Epoch: 5230/20000, Loss: 0.00002914\n",
      "Epoch: 5240/20000, Loss: 0.00003977\n",
      "Epoch: 5250/20000, Loss: 0.00003444\n",
      "Epoch: 5260/20000, Loss: 0.00003023\n",
      "Epoch: 5270/20000, Loss: 0.00002775\n",
      "Epoch: 5280/20000, Loss: 0.00002696\n",
      "Epoch: 5290/20000, Loss: 0.00002869\n",
      "Epoch: 5300/20000, Loss: 0.00010414\n",
      "Epoch: 5310/20000, Loss: 0.00005904\n",
      "Epoch: 5320/20000, Loss: 0.00004834\n",
      "Epoch: 5330/20000, Loss: 0.00003889\n",
      "Epoch: 5340/20000, Loss: 0.00002990\n",
      "Epoch: 5350/20000, Loss: 0.00002959\n",
      "Epoch: 5360/20000, Loss: 0.00004530\n",
      "Epoch: 5370/20000, Loss: 0.00009430\n",
      "Epoch: 5380/20000, Loss: 0.00004224\n",
      "Epoch: 5390/20000, Loss: 0.00003288\n",
      "Epoch: 5400/20000, Loss: 0.00002894\n",
      "Epoch: 5410/20000, Loss: 0.00002560\n",
      "Epoch: 5420/20000, Loss: 0.00002796\n",
      "Epoch: 5430/20000, Loss: 0.00006070\n",
      "Epoch: 5440/20000, Loss: 0.00011456\n",
      "Epoch: 5450/20000, Loss: 0.00005632\n",
      "Epoch: 5460/20000, Loss: 0.00003433\n",
      "Epoch: 5470/20000, Loss: 0.00002957\n",
      "Epoch: 5480/20000, Loss: 0.00002760\n",
      "Epoch: 5490/20000, Loss: 0.00002512\n",
      "Epoch: 5500/20000, Loss: 0.00002747\n",
      "Epoch: 5510/20000, Loss: 0.00006796\n",
      "Epoch: 5520/20000, Loss: 0.00004422\n",
      "Epoch: 5530/20000, Loss: 0.00002950\n",
      "Epoch: 5540/20000, Loss: 0.00002734\n",
      "Epoch: 5550/20000, Loss: 0.00002493\n",
      "Epoch: 5560/20000, Loss: 0.00002845\n",
      "Epoch: 5570/20000, Loss: 0.00012611\n",
      "Epoch: 5580/20000, Loss: 0.00003755\n",
      "Epoch: 5590/20000, Loss: 0.00003514\n",
      "Epoch: 5600/20000, Loss: 0.00002878\n",
      "Epoch: 5610/20000, Loss: 0.00002630\n",
      "Epoch: 5620/20000, Loss: 0.00002392\n",
      "Epoch: 5630/20000, Loss: 0.00002321\n",
      "Epoch: 5640/20000, Loss: 0.00002294\n",
      "Epoch: 5650/20000, Loss: 0.00002310\n",
      "Epoch: 5660/20000, Loss: 0.00003976\n",
      "Epoch: 5670/20000, Loss: 0.00022002\n",
      "Epoch: 5680/20000, Loss: 0.00003365\n",
      "Epoch: 5690/20000, Loss: 0.00004045\n",
      "Epoch: 5700/20000, Loss: 0.00002719\n",
      "Epoch: 5710/20000, Loss: 0.00002414\n",
      "Epoch: 5720/20000, Loss: 0.00002318\n",
      "Epoch: 5730/20000, Loss: 0.00002902\n",
      "Epoch: 5740/20000, Loss: 0.00007378\n",
      "Epoch: 5750/20000, Loss: 0.00002469\n",
      "Epoch: 5760/20000, Loss: 0.00003254\n",
      "Epoch: 5770/20000, Loss: 0.00002401\n",
      "Epoch: 5780/20000, Loss: 0.00002576\n",
      "Epoch: 5790/20000, Loss: 0.00002487\n",
      "Epoch: 5800/20000, Loss: 0.00003331\n",
      "Epoch: 5810/20000, Loss: 0.00009520\n",
      "Epoch: 5820/20000, Loss: 0.00003199\n",
      "Epoch: 5830/20000, Loss: 0.00003122\n",
      "Epoch: 5840/20000, Loss: 0.00002921\n",
      "Epoch: 5850/20000, Loss: 0.00002114\n",
      "Epoch: 5860/20000, Loss: 0.00002201\n",
      "Epoch: 5870/20000, Loss: 0.00002706\n",
      "Epoch: 5880/20000, Loss: 0.00011458\n",
      "Epoch: 5890/20000, Loss: 0.00003667\n",
      "Epoch: 5900/20000, Loss: 0.00005688\n",
      "Epoch: 5910/20000, Loss: 0.00003375\n",
      "Epoch: 5920/20000, Loss: 0.00002903\n",
      "Epoch: 5930/20000, Loss: 0.00002492\n",
      "Epoch: 5940/20000, Loss: 0.00002351\n",
      "Epoch: 5950/20000, Loss: 0.00003731\n",
      "Epoch: 5960/20000, Loss: 0.00007394\n",
      "Epoch: 5970/20000, Loss: 0.00002799\n",
      "Epoch: 5980/20000, Loss: 0.00007051\n",
      "Epoch: 5990/20000, Loss: 0.00007340\n",
      "Epoch: 6000/20000, Loss: 0.00002597\n",
      "Epoch: 6010/20000, Loss: 0.00002585\n",
      "Epoch: 6020/20000, Loss: 0.00002008\n",
      "Epoch: 6030/20000, Loss: 0.00002030\n",
      "Epoch: 6040/20000, Loss: 0.00002002\n",
      "Epoch: 6050/20000, Loss: 0.00002332\n",
      "Epoch: 6060/20000, Loss: 0.00010967\n",
      "Epoch: 6070/20000, Loss: 0.00004144\n",
      "Epoch: 6080/20000, Loss: 0.00003798\n",
      "Epoch: 6090/20000, Loss: 0.00001956\n",
      "Epoch: 6100/20000, Loss: 0.00002051\n",
      "Epoch: 6110/20000, Loss: 0.00001992\n",
      "Epoch: 6120/20000, Loss: 0.00001927\n",
      "Epoch: 6130/20000, Loss: 0.00001903\n",
      "Epoch: 6140/20000, Loss: 0.00001903\n",
      "Epoch: 6150/20000, Loss: 0.00001879\n",
      "Epoch: 6160/20000, Loss: 0.00001872\n",
      "Epoch: 6170/20000, Loss: 0.00001995\n",
      "Epoch: 6180/20000, Loss: 0.00015066\n",
      "Epoch: 6190/20000, Loss: 0.00013008\n",
      "Epoch: 6200/20000, Loss: 0.00004385\n",
      "Epoch: 6210/20000, Loss: 0.00003182\n",
      "Epoch: 6220/20000, Loss: 0.00002585\n",
      "Epoch: 6230/20000, Loss: 0.00002171\n",
      "Epoch: 6240/20000, Loss: 0.00001937\n",
      "Epoch: 6250/20000, Loss: 0.00001868\n",
      "Epoch: 6260/20000, Loss: 0.00001842\n",
      "Epoch: 6270/20000, Loss: 0.00001825\n",
      "Epoch: 6280/20000, Loss: 0.00001813\n",
      "Epoch: 6290/20000, Loss: 0.00001805\n",
      "Epoch: 6300/20000, Loss: 0.00001803\n",
      "Epoch: 6310/20000, Loss: 0.00001806\n",
      "Epoch: 6320/20000, Loss: 0.00001821\n",
      "Epoch: 6330/20000, Loss: 0.00003470\n",
      "Epoch: 6340/20000, Loss: 0.00014823\n",
      "Epoch: 6350/20000, Loss: 0.00004846\n",
      "Epoch: 6360/20000, Loss: 0.00003691\n",
      "Epoch: 6370/20000, Loss: 0.00002347\n",
      "Epoch: 6380/20000, Loss: 0.00002117\n",
      "Epoch: 6390/20000, Loss: 0.00002233\n",
      "Epoch: 6400/20000, Loss: 0.00005569\n",
      "Epoch: 6410/20000, Loss: 0.00004044\n",
      "Epoch: 6420/20000, Loss: 0.00002969\n",
      "Epoch: 6430/20000, Loss: 0.00002430\n",
      "Epoch: 6440/20000, Loss: 0.00001825\n",
      "Epoch: 6450/20000, Loss: 0.00001977\n",
      "Epoch: 6460/20000, Loss: 0.00002114\n",
      "Epoch: 6470/20000, Loss: 0.00004439\n",
      "Epoch: 6480/20000, Loss: 0.00009092\n",
      "Epoch: 6490/20000, Loss: 0.00003782\n",
      "Epoch: 6500/20000, Loss: 0.00002067\n",
      "Epoch: 6510/20000, Loss: 0.00001739\n",
      "Epoch: 6520/20000, Loss: 0.00001867\n",
      "Epoch: 6530/20000, Loss: 0.00002139\n",
      "Epoch: 6540/20000, Loss: 0.00004697\n",
      "Epoch: 6550/20000, Loss: 0.00009407\n",
      "Epoch: 6560/20000, Loss: 0.00003809\n",
      "Epoch: 6570/20000, Loss: 0.00002181\n",
      "Epoch: 6580/20000, Loss: 0.00002058\n",
      "Epoch: 6590/20000, Loss: 0.00001723\n",
      "Epoch: 6600/20000, Loss: 0.00001993\n",
      "Epoch: 6610/20000, Loss: 0.00003709\n",
      "Epoch: 6620/20000, Loss: 0.00015576\n",
      "Epoch: 6630/20000, Loss: 0.00006748\n",
      "Epoch: 6640/20000, Loss: 0.00003259\n",
      "Epoch: 6650/20000, Loss: 0.00001867\n",
      "Epoch: 6660/20000, Loss: 0.00001877\n",
      "Epoch: 6670/20000, Loss: 0.00001691\n",
      "Epoch: 6680/20000, Loss: 0.00001654\n",
      "Epoch: 6690/20000, Loss: 0.00001624\n",
      "Epoch: 6700/20000, Loss: 0.00001740\n",
      "Epoch: 6710/20000, Loss: 0.00008691\n",
      "Epoch: 6720/20000, Loss: 0.00012254\n",
      "Epoch: 6730/20000, Loss: 0.00006176\n",
      "Epoch: 6740/20000, Loss: 0.00002943\n",
      "Epoch: 6750/20000, Loss: 0.00001639\n",
      "Epoch: 6760/20000, Loss: 0.00001848\n",
      "Epoch: 6770/20000, Loss: 0.00001616\n",
      "Epoch: 6780/20000, Loss: 0.00001621\n",
      "Epoch: 6790/20000, Loss: 0.00001586\n",
      "Epoch: 6800/20000, Loss: 0.00001598\n",
      "Epoch: 6810/20000, Loss: 0.00002009\n",
      "Epoch: 6820/20000, Loss: 0.00017115\n",
      "Epoch: 6830/20000, Loss: 0.00007704\n",
      "Epoch: 6840/20000, Loss: 0.00002894\n",
      "Epoch: 6850/20000, Loss: 0.00002132\n",
      "Epoch: 6860/20000, Loss: 0.00001702\n",
      "Epoch: 6870/20000, Loss: 0.00001682\n",
      "Epoch: 6880/20000, Loss: 0.00001587\n",
      "Epoch: 6890/20000, Loss: 0.00001548\n",
      "Epoch: 6900/20000, Loss: 0.00001549\n"
     ]
    },
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Epoch: 6910/20000, Loss: 0.00001581\n",
      "Epoch: 6920/20000, Loss: 0.00002661\n",
      "Epoch: 6930/20000, Loss: 0.00023293\n",
      "Epoch: 6940/20000, Loss: 0.00008914\n",
      "Epoch: 6950/20000, Loss: 0.00002816\n",
      "Epoch: 6960/20000, Loss: 0.00001993\n",
      "Epoch: 6970/20000, Loss: 0.00001744\n",
      "Epoch: 6980/20000, Loss: 0.00001609\n",
      "Epoch: 6990/20000, Loss: 0.00001558\n",
      "Epoch: 7000/20000, Loss: 0.00001532\n",
      "Epoch: 7010/20000, Loss: 0.00001514\n",
      "Epoch: 7020/20000, Loss: 0.00001513\n",
      "Epoch: 7030/20000, Loss: 0.00001540\n",
      "Epoch: 7040/20000, Loss: 0.00002561\n",
      "Epoch: 7050/20000, Loss: 0.00025346\n",
      "Epoch: 7060/20000, Loss: 0.00004621\n",
      "Epoch: 7070/20000, Loss: 0.00004193\n",
      "Epoch: 7080/20000, Loss: 0.00001624\n",
      "Epoch: 7090/20000, Loss: 0.00001900\n",
      "Epoch: 7100/20000, Loss: 0.00001520\n",
      "Epoch: 7110/20000, Loss: 0.00001510\n",
      "Epoch: 7120/20000, Loss: 0.00001487\n",
      "Epoch: 7130/20000, Loss: 0.00001495\n",
      "Epoch: 7140/20000, Loss: 0.00002251\n",
      "Epoch: 7150/20000, Loss: 0.00026652\n",
      "Epoch: 7160/20000, Loss: 0.00004281\n",
      "Epoch: 7170/20000, Loss: 0.00002911\n",
      "Epoch: 7180/20000, Loss: 0.00001905\n",
      "Epoch: 7190/20000, Loss: 0.00001680\n",
      "Epoch: 7200/20000, Loss: 0.00001615\n",
      "Epoch: 7210/20000, Loss: 0.00001497\n",
      "Epoch: 7220/20000, Loss: 0.00001466\n",
      "Epoch: 7230/20000, Loss: 0.00001467\n",
      "Epoch: 7240/20000, Loss: 0.00001704\n",
      "Epoch: 7250/20000, Loss: 0.00010743\n",
      "Epoch: 7260/20000, Loss: 0.00003687\n",
      "Epoch: 7270/20000, Loss: 0.00002589\n",
      "Epoch: 7280/20000, Loss: 0.00002429\n",
      "Epoch: 7290/20000, Loss: 0.00001626\n",
      "Epoch: 7300/20000, Loss: 0.00001525\n",
      "Epoch: 7310/20000, Loss: 0.00001464\n",
      "Epoch: 7320/20000, Loss: 0.00001447\n",
      "Epoch: 7330/20000, Loss: 0.00001425\n",
      "Epoch: 7340/20000, Loss: 0.00001426\n",
      "Epoch: 7350/20000, Loss: 0.00001456\n",
      "Epoch: 7360/20000, Loss: 0.00002426\n",
      "Epoch: 7370/20000, Loss: 0.00025273\n",
      "Epoch: 7380/20000, Loss: 0.00009198\n",
      "Epoch: 7390/20000, Loss: 0.00002464\n",
      "Epoch: 7400/20000, Loss: 0.00001951\n",
      "Epoch: 7410/20000, Loss: 0.00001714\n",
      "Epoch: 7420/20000, Loss: 0.00001557\n",
      "Epoch: 7430/20000, Loss: 0.00001503\n",
      "Epoch: 7440/20000, Loss: 0.00001426\n",
      "Epoch: 7450/20000, Loss: 0.00001407\n",
      "Epoch: 7460/20000, Loss: 0.00001401\n",
      "Epoch: 7470/20000, Loss: 0.00001397\n",
      "Epoch: 7480/20000, Loss: 0.00001524\n",
      "Epoch: 7490/20000, Loss: 0.00008441\n",
      "Epoch: 7500/20000, Loss: 0.00005476\n",
      "Epoch: 7510/20000, Loss: 0.00003168\n",
      "Epoch: 7520/20000, Loss: 0.00002977\n",
      "Epoch: 7530/20000, Loss: 0.00001457\n",
      "Epoch: 7540/20000, Loss: 0.00001703\n",
      "Epoch: 7550/20000, Loss: 0.00001555\n",
      "Epoch: 7560/20000, Loss: 0.00002334\n",
      "Epoch: 7570/20000, Loss: 0.00010053\n",
      "Epoch: 7580/20000, Loss: 0.00001790\n",
      "Epoch: 7590/20000, Loss: 0.00001707\n",
      "Epoch: 7600/20000, Loss: 0.00001870\n",
      "Epoch: 7610/20000, Loss: 0.00001545\n",
      "Epoch: 7620/20000, Loss: 0.00001450\n",
      "Epoch: 7630/20000, Loss: 0.00001435\n",
      "Epoch: 7640/20000, Loss: 0.00001378\n",
      "Epoch: 7650/20000, Loss: 0.00001626\n",
      "Epoch: 7660/20000, Loss: 0.00014309\n",
      "Epoch: 7670/20000, Loss: 0.00007075\n",
      "Epoch: 7680/20000, Loss: 0.00005028\n",
      "Epoch: 7690/20000, Loss: 0.00002822\n",
      "Epoch: 7700/20000, Loss: 0.00001532\n",
      "Epoch: 7710/20000, Loss: 0.00001569\n",
      "Epoch: 7720/20000, Loss: 0.00001428\n",
      "Epoch: 7730/20000, Loss: 0.00001352\n",
      "Epoch: 7740/20000, Loss: 0.00001344\n",
      "Epoch: 7750/20000, Loss: 0.00001339\n",
      "Epoch: 7760/20000, Loss: 0.00001337\n",
      "Epoch: 7770/20000, Loss: 0.00001369\n",
      "Epoch: 7780/20000, Loss: 0.00003166\n",
      "Epoch: 7790/20000, Loss: 0.00008173\n",
      "Epoch: 7800/20000, Loss: 0.00003288\n",
      "Epoch: 7810/20000, Loss: 0.00002021\n",
      "Epoch: 7820/20000, Loss: 0.00001649\n",
      "Epoch: 7830/20000, Loss: 0.00001447\n",
      "Epoch: 7840/20000, Loss: 0.00002771\n",
      "Epoch: 7850/20000, Loss: 0.00020661\n",
      "Epoch: 7860/20000, Loss: 0.00007031\n",
      "Epoch: 7870/20000, Loss: 0.00002864\n",
      "Epoch: 7880/20000, Loss: 0.00001662\n",
      "Epoch: 7890/20000, Loss: 0.00001529\n",
      "Epoch: 7900/20000, Loss: 0.00001445\n",
      "Epoch: 7910/20000, Loss: 0.00001331\n",
      "Epoch: 7920/20000, Loss: 0.00001341\n",
      "Epoch: 7930/20000, Loss: 0.00001346\n",
      "Epoch: 7940/20000, Loss: 0.00001687\n",
      "Epoch: 7950/20000, Loss: 0.00009685\n",
      "Epoch: 7960/20000, Loss: 0.00004537\n",
      "Epoch: 7970/20000, Loss: 0.00003154\n",
      "Epoch: 7980/20000, Loss: 0.00001629\n",
      "Epoch: 7990/20000, Loss: 0.00001518\n",
      "Epoch: 8000/20000, Loss: 0.00001424\n",
      "Epoch: 8010/20000, Loss: 0.00001719\n",
      "Epoch: 8020/20000, Loss: 0.00006505\n",
      "Epoch: 8030/20000, Loss: 0.00005323\n",
      "Epoch: 8040/20000, Loss: 0.00002909\n",
      "Epoch: 8050/20000, Loss: 0.00002022\n",
      "Epoch: 8060/20000, Loss: 0.00001690\n",
      "Epoch: 8070/20000, Loss: 0.00001390\n",
      "Epoch: 8080/20000, Loss: 0.00001372\n",
      "Epoch: 8090/20000, Loss: 0.00001550\n",
      "Epoch: 8100/20000, Loss: 0.00003031\n",
      "Epoch: 8110/20000, Loss: 0.00012056\n",
      "Epoch: 8120/20000, Loss: 0.00004004\n",
      "Epoch: 8130/20000, Loss: 0.00002327\n",
      "Epoch: 8140/20000, Loss: 0.00001586\n",
      "Epoch: 8150/20000, Loss: 0.00001396\n",
      "Epoch: 8160/20000, Loss: 0.00001384\n",
      "Epoch: 8170/20000, Loss: 0.00001382\n",
      "Epoch: 8180/20000, Loss: 0.00002530\n",
      "Epoch: 8190/20000, Loss: 0.00021382\n",
      "Epoch: 8200/20000, Loss: 0.00007554\n",
      "Epoch: 8210/20000, Loss: 0.00001790\n",
      "Epoch: 8220/20000, Loss: 0.00001883\n",
      "Epoch: 8230/20000, Loss: 0.00001631\n",
      "Epoch: 8240/20000, Loss: 0.00001386\n",
      "Epoch: 8250/20000, Loss: 0.00001306\n",
      "Epoch: 8260/20000, Loss: 0.00001303\n",
      "Epoch: 8270/20000, Loss: 0.00002371\n",
      "Epoch: 8280/20000, Loss: 0.00008382\n",
      "Epoch: 8290/20000, Loss: 0.00002285\n",
      "Epoch: 8300/20000, Loss: 0.00001734\n",
      "Epoch: 8310/20000, Loss: 0.00001698\n",
      "Epoch: 8320/20000, Loss: 0.00001418\n",
      "Epoch: 8330/20000, Loss: 0.00001803\n",
      "Epoch: 8340/20000, Loss: 0.00009300\n",
      "Epoch: 8350/20000, Loss: 0.00004646\n",
      "Epoch: 8360/20000, Loss: 0.00002753\n",
      "Epoch: 8370/20000, Loss: 0.00001711\n",
      "Epoch: 8380/20000, Loss: 0.00001260\n",
      "Epoch: 8390/20000, Loss: 0.00001275\n",
      "Epoch: 8400/20000, Loss: 0.00001695\n",
      "Epoch: 8410/20000, Loss: 0.00011573\n",
      "Epoch: 8420/20000, Loss: 0.00002816\n",
      "Epoch: 8430/20000, Loss: 0.00003045\n",
      "Epoch: 8440/20000, Loss: 0.00002148\n",
      "Epoch: 8450/20000, Loss: 0.00001361\n",
      "Epoch: 8460/20000, Loss: 0.00001273\n",
      "Epoch: 8470/20000, Loss: 0.00001271\n",
      "Epoch: 8480/20000, Loss: 0.00001252\n",
      "Epoch: 8490/20000, Loss: 0.00001269\n",
      "Epoch: 8500/20000, Loss: 0.00001983\n",
      "Epoch: 8510/20000, Loss: 0.00018150\n",
      "Epoch: 8520/20000, Loss: 0.00005818\n",
      "Epoch: 8530/20000, Loss: 0.00001770\n",
      "Epoch: 8540/20000, Loss: 0.00001814\n",
      "Epoch: 8550/20000, Loss: 0.00001461\n",
      "Epoch: 8560/20000, Loss: 0.00001272\n",
      "Epoch: 8570/20000, Loss: 0.00001268\n",
      "Epoch: 8580/20000, Loss: 0.00001255\n",
      "Epoch: 8590/20000, Loss: 0.00001453\n",
      "Epoch: 8600/20000, Loss: 0.00006374\n",
      "Epoch: 8610/20000, Loss: 0.00006634\n",
      "Epoch: 8620/20000, Loss: 0.00002213\n",
      "Epoch: 8630/20000, Loss: 0.00001837\n",
      "Epoch: 8640/20000, Loss: 0.00001515\n",
      "Epoch: 8650/20000, Loss: 0.00001261\n",
      "Epoch: 8660/20000, Loss: 0.00001224\n",
      "Epoch: 8670/20000, Loss: 0.00001236\n",
      "Epoch: 8680/20000, Loss: 0.00001246\n",
      "Epoch: 8690/20000, Loss: 0.00002209\n",
      "Epoch: 8700/20000, Loss: 0.00011190\n",
      "Epoch: 8710/20000, Loss: 0.00003806\n",
      "Epoch: 8720/20000, Loss: 0.00002666\n",
      "Epoch: 8730/20000, Loss: 0.00001475\n",
      "Epoch: 8740/20000, Loss: 0.00001275\n",
      "Epoch: 8750/20000, Loss: 0.00001227\n",
      "Epoch: 8760/20000, Loss: 0.00001324\n",
      "Epoch: 8770/20000, Loss: 0.00002918\n",
      "Epoch: 8780/20000, Loss: 0.00017784\n",
      "Epoch: 8790/20000, Loss: 0.00005216\n",
      "Epoch: 8800/20000, Loss: 0.00002771\n",
      "Epoch: 8810/20000, Loss: 0.00001737\n",
      "Epoch: 8820/20000, Loss: 0.00001418\n",
      "Epoch: 8830/20000, Loss: 0.00001253\n",
      "Epoch: 8840/20000, Loss: 0.00001232\n",
      "Epoch: 8850/20000, Loss: 0.00001258\n",
      "Epoch: 8860/20000, Loss: 0.00001349\n",
      "Epoch: 8870/20000, Loss: 0.00004351\n",
      "Epoch: 8880/20000, Loss: 0.00008757\n",
      "Epoch: 8890/20000, Loss: 0.00002156\n",
      "Epoch: 8900/20000, Loss: 0.00002255\n",
      "Epoch: 8910/20000, Loss: 0.00001493\n",
      "Epoch: 8920/20000, Loss: 0.00001395\n",
      "Epoch: 8930/20000, Loss: 0.00001280\n",
      "Epoch: 8940/20000, Loss: 0.00001217\n",
      "Epoch: 8950/20000, Loss: 0.00001364\n",
      "Epoch: 8960/20000, Loss: 0.00005831\n",
      "Epoch: 8970/20000, Loss: 0.00011265\n",
      "Epoch: 8980/20000, Loss: 0.00003187\n",
      "Epoch: 8990/20000, Loss: 0.00001373\n",
      "Epoch: 9000/20000, Loss: 0.00001284\n",
      "Epoch: 9010/20000, Loss: 0.00001198\n",
      "Epoch: 9020/20000, Loss: 0.00001242\n",
      "Epoch: 9030/20000, Loss: 0.00001199\n",
      "Epoch: 9040/20000, Loss: 0.00001196\n",
      "Epoch: 9050/20000, Loss: 0.00001260\n",
      "Epoch: 9060/20000, Loss: 0.00001633\n",
      "Epoch: 9070/20000, Loss: 0.00013560\n",
      "Epoch: 9080/20000, Loss: 0.00006239\n",
      "Epoch: 9090/20000, Loss: 0.00001950\n",
      "Epoch: 9100/20000, Loss: 0.00001969\n",
      "Epoch: 9110/20000, Loss: 0.00001446\n",
      "Epoch: 9120/20000, Loss: 0.00001219\n",
      "Epoch: 9130/20000, Loss: 0.00001187\n",
      "Epoch: 9140/20000, Loss: 0.00001160\n",
      "Epoch: 9150/20000, Loss: 0.00001163\n",
      "Epoch: 9160/20000, Loss: 0.00001177\n",
      "Epoch: 9170/20000, Loss: 0.00001545\n",
      "Epoch: 9180/20000, Loss: 0.00015422\n",
      "Epoch: 9190/20000, Loss: 0.00005522\n"
     ]
    },
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Epoch: 9200/20000, Loss: 0.00003885\n",
      "Epoch: 9210/20000, Loss: 0.00001797\n",
      "Epoch: 9220/20000, Loss: 0.00001440\n",
      "Epoch: 9230/20000, Loss: 0.00001286\n",
      "Epoch: 9240/20000, Loss: 0.00001241\n",
      "Epoch: 9250/20000, Loss: 0.00001162\n",
      "Epoch: 9260/20000, Loss: 0.00001168\n",
      "Epoch: 9270/20000, Loss: 0.00001161\n",
      "Epoch: 9280/20000, Loss: 0.00001348\n",
      "Epoch: 9290/20000, Loss: 0.00007565\n",
      "Epoch: 9300/20000, Loss: 0.00003853\n",
      "Epoch: 9310/20000, Loss: 0.00003616\n",
      "Epoch: 9320/20000, Loss: 0.00001259\n",
      "Epoch: 9330/20000, Loss: 0.00001306\n",
      "Epoch: 9340/20000, Loss: 0.00001255\n",
      "Epoch: 9350/20000, Loss: 0.00001199\n",
      "Epoch: 9360/20000, Loss: 0.00001328\n",
      "Epoch: 9370/20000, Loss: 0.00002995\n",
      "Epoch: 9380/20000, Loss: 0.00018363\n",
      "Epoch: 9390/20000, Loss: 0.00006340\n",
      "Epoch: 9400/20000, Loss: 0.00002402\n",
      "Epoch: 9410/20000, Loss: 0.00001372\n",
      "Epoch: 9420/20000, Loss: 0.00001392\n",
      "Epoch: 9430/20000, Loss: 0.00001291\n",
      "Epoch: 9440/20000, Loss: 0.00001206\n",
      "Epoch: 9450/20000, Loss: 0.00001933\n",
      "Epoch: 9460/20000, Loss: 0.00001445\n",
      "Epoch: 9470/20000, Loss: 0.00001924\n",
      "Epoch: 9480/20000, Loss: 0.00005664\n",
      "Epoch: 9490/20000, Loss: 0.00003755\n",
      "Epoch: 9500/20000, Loss: 0.00001589\n",
      "Epoch: 9510/20000, Loss: 0.00001821\n",
      "Epoch: 9520/20000, Loss: 0.00001453\n",
      "Epoch: 9530/20000, Loss: 0.00001361\n",
      "Epoch: 9540/20000, Loss: 0.00002231\n",
      "Epoch: 9550/20000, Loss: 0.00011211\n",
      "Epoch: 9560/20000, Loss: 0.00002244\n",
      "Epoch: 9570/20000, Loss: 0.00001712\n",
      "Epoch: 9580/20000, Loss: 0.00001492\n",
      "Epoch: 9590/20000, Loss: 0.00001336\n",
      "Epoch: 9600/20000, Loss: 0.00001321\n",
      "Epoch: 9610/20000, Loss: 0.00001270\n",
      "Epoch: 9620/20000, Loss: 0.00002161\n",
      "Epoch: 9630/20000, Loss: 0.00011349\n",
      "Epoch: 9640/20000, Loss: 0.00003860\n",
      "Epoch: 9650/20000, Loss: 0.00001763\n",
      "Epoch: 9660/20000, Loss: 0.00001420\n",
      "Epoch: 9670/20000, Loss: 0.00001292\n",
      "Epoch: 9680/20000, Loss: 0.00001191\n",
      "Epoch: 9690/20000, Loss: 0.00001150\n",
      "Epoch: 9700/20000, Loss: 0.00001627\n",
      "Epoch: 9710/20000, Loss: 0.00015336\n",
      "Epoch: 9720/20000, Loss: 0.00005502\n",
      "Epoch: 9730/20000, Loss: 0.00003205\n",
      "Epoch: 9740/20000, Loss: 0.00001945\n",
      "Epoch: 9750/20000, Loss: 0.00001269\n",
      "Epoch: 9760/20000, Loss: 0.00001225\n",
      "Epoch: 9770/20000, Loss: 0.00001140\n",
      "Epoch: 9780/20000, Loss: 0.00001112\n",
      "Epoch: 9790/20000, Loss: 0.00001099\n",
      "Epoch: 9800/20000, Loss: 0.00001112\n",
      "Epoch: 9810/20000, Loss: 0.00001500\n",
      "Epoch: 9820/20000, Loss: 0.00010675\n",
      "Epoch: 9830/20000, Loss: 0.00010121\n",
      "Epoch: 9840/20000, Loss: 0.00002571\n",
      "Epoch: 9850/20000, Loss: 0.00002156\n",
      "Epoch: 9860/20000, Loss: 0.00001200\n",
      "Epoch: 9870/20000, Loss: 0.00001228\n",
      "Epoch: 9880/20000, Loss: 0.00001120\n",
      "Epoch: 9890/20000, Loss: 0.00001097\n",
      "Epoch: 9900/20000, Loss: 0.00001096\n",
      "Epoch: 9910/20000, Loss: 0.00001155\n",
      "Epoch: 9920/20000, Loss: 0.00007915\n",
      "Epoch: 9930/20000, Loss: 0.00002068\n",
      "Epoch: 9940/20000, Loss: 0.00004344\n",
      "Epoch: 9950/20000, Loss: 0.00003011\n",
      "Epoch: 9960/20000, Loss: 0.00001692\n",
      "Epoch: 9970/20000, Loss: 0.00001283\n",
      "Epoch: 9980/20000, Loss: 0.00001192\n",
      "Epoch: 9990/20000, Loss: 0.00001119\n",
      "Epoch: 10000/20000, Loss: 0.00001101\n",
      "Epoch: 10010/20000, Loss: 0.00001086\n",
      "Epoch: 10020/20000, Loss: 0.00001084\n",
      "Epoch: 10030/20000, Loss: 0.00001119\n",
      "Epoch: 10040/20000, Loss: 0.00001535\n",
      "Epoch: 10050/20000, Loss: 0.00001158\n",
      "Epoch: 10060/20000, Loss: 0.00001091\n",
      "Epoch: 10070/20000, Loss: 0.00001318\n",
      "Epoch: 10080/20000, Loss: 0.00001794\n",
      "Epoch: 10090/20000, Loss: 0.00001235\n",
      "Epoch: 10100/20000, Loss: 0.00001628\n",
      "Epoch: 10110/20000, Loss: 0.00009067\n",
      "Epoch: 10120/20000, Loss: 0.00003279\n",
      "Epoch: 10130/20000, Loss: 0.00003249\n",
      "Epoch: 10140/20000, Loss: 0.00001559\n",
      "Epoch: 10150/20000, Loss: 0.00001370\n",
      "Epoch: 10160/20000, Loss: 0.00001151\n",
      "Epoch: 10170/20000, Loss: 0.00001146\n",
      "Epoch: 10180/20000, Loss: 0.00001575\n",
      "Epoch: 10190/20000, Loss: 0.00006363\n",
      "Epoch: 10200/20000, Loss: 0.00007484\n",
      "Epoch: 10210/20000, Loss: 0.00003607\n",
      "Epoch: 10220/20000, Loss: 0.00001886\n",
      "Epoch: 10230/20000, Loss: 0.00001418\n",
      "Epoch: 10240/20000, Loss: 0.00001373\n",
      "Epoch: 10250/20000, Loss: 0.00001124\n",
      "Epoch: 10260/20000, Loss: 0.00001292\n",
      "Epoch: 10270/20000, Loss: 0.00004155\n",
      "Epoch: 10280/20000, Loss: 0.00014745\n",
      "Epoch: 10290/20000, Loss: 0.00002037\n",
      "Epoch: 10300/20000, Loss: 0.00002060\n",
      "Epoch: 10310/20000, Loss: 0.00001649\n",
      "Epoch: 10320/20000, Loss: 0.00001218\n",
      "Epoch: 10330/20000, Loss: 0.00001106\n",
      "Epoch: 10340/20000, Loss: 0.00001081\n",
      "Epoch: 10350/20000, Loss: 0.00001108\n",
      "Epoch: 10360/20000, Loss: 0.00002088\n",
      "Epoch: 10370/20000, Loss: 0.00005893\n",
      "Epoch: 10380/20000, Loss: 0.00001830\n",
      "Epoch: 10390/20000, Loss: 0.00001711\n",
      "Epoch: 10400/20000, Loss: 0.00001192\n",
      "Epoch: 10410/20000, Loss: 0.00001166\n",
      "Epoch: 10420/20000, Loss: 0.00002732\n",
      "Epoch: 10430/20000, Loss: 0.00014858\n",
      "Epoch: 10440/20000, Loss: 0.00002790\n",
      "Epoch: 10450/20000, Loss: 0.00002662\n",
      "Epoch: 10460/20000, Loss: 0.00001497\n",
      "Epoch: 10470/20000, Loss: 0.00001225\n",
      "Epoch: 10480/20000, Loss: 0.00001137\n",
      "Epoch: 10490/20000, Loss: 0.00001066\n",
      "Epoch: 10500/20000, Loss: 0.00001068\n",
      "Epoch: 10510/20000, Loss: 0.00001135\n",
      "Epoch: 10520/20000, Loss: 0.00002940\n",
      "Epoch: 10530/20000, Loss: 0.00021068\n",
      "Epoch: 10540/20000, Loss: 0.00004303\n",
      "Epoch: 10550/20000, Loss: 0.00002248\n",
      "Epoch: 10560/20000, Loss: 0.00002025\n",
      "Epoch: 10570/20000, Loss: 0.00001255\n",
      "Epoch: 10580/20000, Loss: 0.00001135\n",
      "Epoch: 10590/20000, Loss: 0.00001121\n",
      "Epoch: 10600/20000, Loss: 0.00001075\n",
      "Epoch: 10610/20000, Loss: 0.00001044\n",
      "Epoch: 10620/20000, Loss: 0.00001046\n",
      "Epoch: 10630/20000, Loss: 0.00001042\n",
      "Epoch: 10640/20000, Loss: 0.00001075\n",
      "Epoch: 10650/20000, Loss: 0.00002465\n",
      "Epoch: 10660/20000, Loss: 0.00017955\n",
      "Epoch: 10670/20000, Loss: 0.00015180\n",
      "Epoch: 10680/20000, Loss: 0.00004573\n",
      "Epoch: 10690/20000, Loss: 0.00001757\n",
      "Epoch: 10700/20000, Loss: 0.00001251\n",
      "Epoch: 10710/20000, Loss: 0.00001108\n",
      "Epoch: 10720/20000, Loss: 0.00001063\n",
      "Epoch: 10730/20000, Loss: 0.00001054\n",
      "Epoch: 10740/20000, Loss: 0.00001048\n",
      "Epoch: 10750/20000, Loss: 0.00001043\n",
      "Epoch: 10760/20000, Loss: 0.00001037\n",
      "Epoch: 10770/20000, Loss: 0.00001035\n",
      "Epoch: 10780/20000, Loss: 0.00001033\n",
      "Epoch: 10790/20000, Loss: 0.00001033\n",
      "Epoch: 10800/20000, Loss: 0.00001100\n",
      "Epoch: 10810/20000, Loss: 0.00006530\n",
      "Epoch: 10820/20000, Loss: 0.00005669\n",
      "Epoch: 10830/20000, Loss: 0.00003965\n",
      "Epoch: 10840/20000, Loss: 0.00001932\n",
      "Epoch: 10850/20000, Loss: 0.00001318\n",
      "Epoch: 10860/20000, Loss: 0.00001331\n",
      "Epoch: 10870/20000, Loss: 0.00001119\n",
      "Epoch: 10880/20000, Loss: 0.00001058\n",
      "Epoch: 10890/20000, Loss: 0.00001043\n",
      "Epoch: 10900/20000, Loss: 0.00001036\n",
      "Epoch: 10910/20000, Loss: 0.00001055\n",
      "Epoch: 10920/20000, Loss: 0.00001039\n",
      "Epoch: 10930/20000, Loss: 0.00001031\n",
      "Epoch: 10940/20000, Loss: 0.00001026\n",
      "Epoch: 10950/20000, Loss: 0.00001087\n",
      "Epoch: 10960/20000, Loss: 0.00005135\n",
      "Epoch: 10970/20000, Loss: 0.00008280\n",
      "Epoch: 10980/20000, Loss: 0.00005898\n",
      "Epoch: 10990/20000, Loss: 0.00002471\n",
      "Epoch: 11000/20000, Loss: 0.00001421\n",
      "Epoch: 11010/20000, Loss: 0.00001303\n",
      "Epoch: 11020/20000, Loss: 0.00001096\n",
      "Epoch: 11030/20000, Loss: 0.00001039\n",
      "Epoch: 11040/20000, Loss: 0.00001035\n",
      "Epoch: 11050/20000, Loss: 0.00001028\n",
      "Epoch: 11060/20000, Loss: 0.00001023\n",
      "Epoch: 11070/20000, Loss: 0.00001020\n",
      "Epoch: 11080/20000, Loss: 0.00001018\n",
      "Epoch: 11090/20000, Loss: 0.00001017\n",
      "Epoch: 11100/20000, Loss: 0.00001016\n",
      "Epoch: 11110/20000, Loss: 0.00001098\n",
      "Epoch: 11120/20000, Loss: 0.00002131\n",
      "Epoch: 11130/20000, Loss: 0.00032913\n",
      "Epoch: 11140/20000, Loss: 0.00004961\n",
      "Epoch: 11150/20000, Loss: 0.00002866\n",
      "Epoch: 11160/20000, Loss: 0.00002426\n",
      "Epoch: 11170/20000, Loss: 0.00001476\n",
      "Epoch: 11180/20000, Loss: 0.00001195\n",
      "Epoch: 11190/20000, Loss: 0.00001057\n",
      "Epoch: 11200/20000, Loss: 0.00001054\n",
      "Epoch: 11210/20000, Loss: 0.00001032\n",
      "Epoch: 11220/20000, Loss: 0.00001041\n",
      "Epoch: 11230/20000, Loss: 0.00001022\n",
      "Epoch: 11240/20000, Loss: 0.00001017\n",
      "Epoch: 11250/20000, Loss: 0.00001015\n",
      "Epoch: 11260/20000, Loss: 0.00001014\n",
      "Epoch: 11270/20000, Loss: 0.00001012\n",
      "Epoch: 11280/20000, Loss: 0.00001011\n",
      "Epoch: 11290/20000, Loss: 0.00001010\n",
      "Epoch: 11300/20000, Loss: 0.00001021\n",
      "Epoch: 11310/20000, Loss: 0.00001998\n",
      "Epoch: 11320/20000, Loss: 0.00037893\n",
      "Epoch: 11330/20000, Loss: 0.00007384\n",
      "Epoch: 11340/20000, Loss: 0.00002858\n",
      "Epoch: 11350/20000, Loss: 0.00001535\n",
      "Epoch: 11360/20000, Loss: 0.00001155\n",
      "Epoch: 11370/20000, Loss: 0.00001098\n",
      "Epoch: 11380/20000, Loss: 0.00001046\n",
      "Epoch: 11390/20000, Loss: 0.00001022\n",
      "Epoch: 11400/20000, Loss: 0.00001017\n",
      "Epoch: 11410/20000, Loss: 0.00001012\n",
      "Epoch: 11420/20000, Loss: 0.00001009\n",
      "Epoch: 11430/20000, Loss: 0.00001007\n"
     ]
    },
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Epoch: 11440/20000, Loss: 0.00001012\n",
      "Epoch: 11450/20000, Loss: 0.00001028\n",
      "Epoch: 11460/20000, Loss: 0.00001004\n",
      "Epoch: 11470/20000, Loss: 0.00001003\n",
      "Epoch: 11480/20000, Loss: 0.00001009\n",
      "Epoch: 11490/20000, Loss: 0.00001922\n",
      "Epoch: 11500/20000, Loss: 0.00046367\n"
     ]
    }
   ],
   "source": [
    "# Create LSTM instance\n",
    "lstm = LSTM(input_size, hidden_size, output_size)\n",
    "\n",
    "# Loss and optimizer\n",
    "criterion = nn.MSELoss()\n",
    "optimizer = torch.optim.Adam(lstm.parameters(), lr=0.01)\n",
    "\n",
    "# Training loop\n",
    "for epoch in range(num_epochs):\n",
    "    # Set initial hidden state and cell state\n",
    "    hidden = torch.zeros(1, batch_size, hidden_size)\n",
    "    cell = torch.zeros(1, batch_size, hidden_size)\n",
    "\n",
    "    # Forward pass\n",
    "    output, (hidden, cell) = lstm(input_tensor, (hidden, cell))\n",
    "    loss = criterion(output, target_tensor)\n",
    "\n",
    "    # Backward and optimize\n",
    "    optimizer.zero_grad()\n",
    "    loss.backward()\n",
    "    optimizer.step()\n",
    "\n",
    "    # Print progress\n",
    "    if (epoch+1) % 10 == 0:\n",
    "        print(f'Epoch: {epoch+1}/{num_epochs}, Loss: {loss.item():.8f}')\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "986e4048",
   "metadata": {},
   "outputs": [],
   "source": [
    "print(test_tensor.shape)\n",
    "prediction_tensor = torch.zeros(1, 20, 256).float()\n",
    "print(prediction_tensor.shape)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "60c20ae0",
   "metadata": {},
   "outputs": [],
   "source": [
    "with torch.no_grad():\n",
    "    hidden_pred = torch.zeros(1, batch_size, hidden_size)\n",
    "    cell_pred = torch.zeros(1, batch_size, hidden_size)\n",
    "    prediction, _ = lstm(test_tensor, (hidden_pred, cell_pred))\n",
    "    prediction = prediction.view(1, 1, 256).float()\n",
    "    prediction_tensor[:, 0, :] = prediction\n",
    "    for i in range(19):\n",
    "        hidden_pred = torch.zeros(1, batch_size, hidden_size)\n",
    "        cell_pred = torch.zeros(1, batch_size, hidden_size)\n",
    "        prediction, _ = lstm(test_tensor, (hidden_pred, cell_pred))\n",
    "        prediction = prediction.view(1, 1, 256).float()\n",
    "        prediction_tensor[:, i+1, :] = prediction"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "4a90e52a",
   "metadata": {},
   "source": [
    "### Four different types of error"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "bef6a130",
   "metadata": {},
   "outputs": [],
   "source": [
    "# Exact Solution\n",
    "u_1 = u\n",
    "u_test = u_1.T\n",
    "u_test_full = u_test[80:100, :]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "e2ddbdc2",
   "metadata": {},
   "outputs": [],
   "source": [
    "prediction_tensor = torch.squeeze(prediction_tensor)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "ccf1b971",
   "metadata": {},
   "outputs": [],
   "source": [
    "# Extrapolation\n",
    "\n",
    "k1 = ( prediction_tensor - u_test_full)**2\n",
    "u_test_full_tensor = torch.tensor(u_test_full**2)\n",
    "u_test_full_tensor.shape"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "0f9f7558",
   "metadata": {},
   "source": [
    "### L^2 norm error"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "0c7a201a",
   "metadata": {},
   "outputs": [],
   "source": [
    "# Compute the relative L2 error norm (generalization error)\n",
    "relative_error_test = torch.mean(k1)/ torch.mean(u_test_full_tensor)\n",
    "\n",
    "print(\"Relative Error Test: \", relative_error_test.item(), \"%\")"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "8cb76eb1",
   "metadata": {},
   "source": [
    "### Max absolute norm error"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "323de4e6",
   "metadata": {},
   "outputs": [],
   "source": [
    "R_abs = torch.max(torch.abs(prediction_tensor - u_test_full))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "8c372e5e",
   "metadata": {},
   "outputs": [],
   "source": [
    "print(R_abs)"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "afbe76c9",
   "metadata": {},
   "source": [
    "### Explained variance score"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "d2cb017e",
   "metadata": {},
   "outputs": [],
   "source": [
    "import torch\n",
    "\n",
    "a = prediction_tensor\n",
    "b = u_test_full\n",
    "# Assuming 'a' is your predicted values (model's predictions) and 'b' is the true values (ground truth)\n",
    "# Make sure 'a' and 'b' are PyTorch tensors\n",
    "# a = torch.tensor(a)\n",
    "b = torch.tensor(b)\n",
    "# Calculate the mean of 'b'\n",
    "mean_b = torch.mean(b)\n",
    "\n",
    "# Calculate the Explained Variance Score\n",
    "numerator = torch.var(b - a)  # Variance of the differences between 'b' and 'a'\n",
    "denominator = torch.var(b)    # Variance of 'b'\n",
    "evs = 1 - numerator / denominator\n",
    "\n",
    "print(\"Explained Variance Score:\", evs.item())"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "d74533a9",
   "metadata": {},
   "source": [
    "### Mean absolute error"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "89866f2e",
   "metadata": {},
   "outputs": [],
   "source": [
    "# Compute the relative L2 error norm (generalization error)\n",
    "relative_error_test = torch.mean(torch.abs(prediction_tensor - u_test_full))\n",
    "\n",
    "print(\"Relative Error Test: \", relative_error_test, \"%\")"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "83b467df",
   "metadata": {},
   "source": [
    "### Contour plot for PINN (80 percent) and (20 percentage lem prediction)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "8ae31ab0",
   "metadata": {},
   "outputs": [],
   "source": [
    "print(prediction_tensor.shape)\n",
    "prediction_tensor = torch.squeeze(prediction_tensor)\n",
    "input_tensor = torch.squeeze(input_tensor)\n",
    "\n",
    "conc_u = torch.squeeze(input_tensor)\n",
    "concatenated_tensor = torch.cat((conc_u, prediction_tensor), dim=0)\n",
    "\n",
    "x1 = np.linspace(-1, 1, 256)\n",
    "t1 = np.linspace(0, 1, 99)"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "f646adab",
   "metadata": {},
   "source": [
    "### Snapshot time plots"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "e65b03b6",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "import torch\n",
    "\n",
    "# Create the figure and axis objects with reduced width\n",
    "fig, ax = plt.subplots(figsize=(5, 5))  # You can adjust the width (7 inches) and height (5 inches) as needed\n",
    "\n",
    "\n",
    "\n",
    "\n",
    "final_time_output = prediction_tensor[3, :]\n",
    "final_out = final_time_output.detach().numpy().reshape(-1, 1)\n",
    "final_true = u_1[:, 83].reshape(-1, 1)\n",
    "\n",
    "# Plot the data with red and blue lines, one with dotted and one with solid style\n",
    "ax.plot(x.T, final_out, color='red', linestyle='dotted', linewidth=12, label='Prediction')\n",
    "ax.plot(x.T, final_true, color='blue', linestyle='solid', linewidth=7, label='True')\n",
    "\n",
    "\n",
    "# Set the axis labels with bold font weight\n",
    "ax.set_xlabel(r\"${x}$\", fontsize=26, color='black', fontdict={'weight': 'bold'})\n",
    "ax.set_ylabel(r\"${u(x, t)}$\", fontsize=26, color='black', fontdict={'weight': 'bold'})\n",
    "\n",
    "# Set the title with bold font weight\n",
    "ax.set_title(r\"${t = 0.83}$\", fontsize=26, color='black', fontweight='bold')\n",
    "\n",
    "# Set the number of ticks for x-axis and y-axis to 3\n",
    "ax.set_xticks([-1, 0, 1])\n",
    "ax.set_yticks([-1, 0, 1])\n",
    "\n",
    "# Set tick labels fontweight to bold and increase font size\n",
    "ax.tick_params(axis='both', which='major', labelsize=20, width=2, length=10)\n",
    "\n",
    "# # Set the fontweight for tick labels to bold\n",
    "# for tick in ax.get_xticklabels() + ax.get_yticklabels():\n",
    "#     tick.set_weight('bold')\n",
    "\n",
    "# Set the spines linewidth to bold\n",
    "ax.spines['top'].set_linewidth(2)\n",
    "ax.spines['right'].set_linewidth(2)\n",
    "ax.spines['bottom'].set_linewidth(2)\n",
    "ax.spines['left'].set_linewidth(2)\n",
    "\n",
    "# Set the legend\n",
    "# ax.legend()\n",
    "\n",
    "plt.savefig('LSTM_0.83_20.pdf', dpi=500, bbox_inches=\"tight\")\n",
    "#plt.savefig('lem_0.83_20.png', dpi=500, bbox_inches=\"tight\")\n",
    "# Show the plot\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "d98cd1ee",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "import torch\n",
    "\n",
    "# Create the figure and axis objects with reduced width\n",
    "fig, ax = plt.subplots(figsize=(5, 5))  # You can adjust the width (7 inches) and height (5 inches) as needed\n",
    "\n",
    "\n",
    "\n",
    "final_time_output = prediction_tensor[-2, :]\n",
    "final_out = final_time_output.detach().numpy().reshape(-1, 1)\n",
    "final_true = u_1[:, -2].reshape(-1, 1)\n",
    "\n",
    "# Plot the data with red and blue lines, one with dotted and one with solid style\n",
    "ax.plot(x.T, final_out, color='red', linestyle='dotted', linewidth=12, label='Prediction')\n",
    "ax.plot(x.T, final_true, color='blue', linestyle='solid', linewidth=7, label='True')\n",
    "\n",
    "\n",
    "# Set the axis labels with bold font weight\n",
    "ax.set_xlabel(r\"${x}$\", fontsize=26, color='black', fontdict={'weight': 'bold'})\n",
    "ax.set_ylabel(r\"${u(x, t)}$\", fontsize=26, color='black', fontdict={'weight': 'bold'})\n",
    "\n",
    "# Set the title with bold font weight\n",
    "ax.set_title(r\"${t = 0.98}$\", fontsize=26, color='black', fontweight='bold')\n",
    "\n",
    "# Set the number of ticks for x-axis and y-axis to 3\n",
    "ax.set_xticks([-1, 0, 1])\n",
    "ax.set_yticks([-1, 0, 1])\n",
    "\n",
    "# Set tick labels fontweight to bold and increase font size\n",
    "ax.tick_params(axis='both', which='major', labelsize=20, width=2, length=10)\n",
    "\n",
    "# # Set the fontweight for tick labels to bold\n",
    "# for tick in ax.get_xticklabels() + ax.get_yticklabels():\n",
    "#     tick.set_weight('bold')\n",
    "\n",
    "# Set the spines linewidth to bold\n",
    "ax.spines['top'].set_linewidth(2)\n",
    "ax.spines['right'].set_linewidth(2)\n",
    "ax.spines['bottom'].set_linewidth(2)\n",
    "ax.spines['left'].set_linewidth(2)\n",
    "\n",
    "# Set the legend\n",
    "# ax.legend()\n",
    "\n",
    "plt.savefig('LSTM_0.98_20.pdf', dpi=500, bbox_inches=\"tight\")\n",
    "#plt.savefig('lem_0.98_20.png', dpi=500, bbox_inches=\"tight\")\n",
    "# Show the plot\n",
    "plt.show()\n"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "986fafe0",
   "metadata": {},
   "source": [
    "### Contour plot where 80 percent for PINN solution and 20 percent for LSTM solution"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "6665c9a8",
   "metadata": {},
   "source": [
    "### Exact contour"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "736d32fe",
   "metadata": {},
   "outputs": [],
   "source": [
    "import torch\n",
    "import numpy as np\n",
    "import matplotlib.pyplot as plt\n",
    "from matplotlib.ticker import FixedLocator\n",
    "\n",
    "# Assuming you have defined concatenated_tensor as a PyTorch tensor\n",
    "# concatenated_tensor = torch.cat((tensor1, tensor2), dim=0)\n",
    "\n",
    "# Convert concatenated_tensor to a NumPy array\n",
    "concatenated_array = u_1.T\n",
    "\n",
    "# Define custom color levels\n",
    "x = np.linspace(-1, 1, concatenated_array.shape[1])  # Replace 0 and 1 with your actual x range\n",
    "t = np.linspace(0, 1, concatenated_array.shape[0])  # Replace 0 and 1 with your actual t range\n",
    "X, T = np.meshgrid(x, t)\n",
    "\n",
    "# Define custom color levels using the minimum and maximum from the NumPy array\n",
    "c_levels = np.linspace(np.min(concatenated_array), np.max(concatenated_array), 400)\n",
    "\n",
    "# Plot the contour with interpolated data\n",
    "plt.figure(figsize=(20, 5))\n",
    "plt.pcolormesh(T, X, concatenated_array, shading='auto', cmap='coolwarm')\n",
    "\n",
    "# Set the fontweight for axis labels to regular (not bold)\n",
    "plt.xlabel(\"$t$\", fontsize=26)\n",
    "plt.ylabel(\"$x$\", fontsize=26)\n",
    "plt.title(\"$u(x, t)$\", fontsize=26)\n",
    "\n",
    "# Set tick labels fontweight to regular (not bold) and increase font size\n",
    "plt.tick_params(axis='both', which='major', labelsize=20, width=3, length=10)\n",
    "\n",
    "# Set the fontweight for tick labels to regular (not bold)\n",
    "for tick in plt.gca().get_xticklabels() + plt.gca().get_yticklabels():\n",
    "    tick.set_weight('normal')\n",
    "\n",
    "# Set the number of ticks for x-axis and y-axis to 5\n",
    "num_ticks = 5\n",
    "x_ticks = np.linspace(np.min(T), np.max(T), num_ticks)\n",
    "y_ticks = np.linspace(np.min(X), np.max(X), num_ticks)\n",
    "\n",
    "plt.gca().xaxis.set_major_locator(FixedLocator(x_ticks))\n",
    "plt.gca().yaxis.set_major_locator(FixedLocator(y_ticks))\n",
    "\n",
    "cbar1 = plt.colorbar()\n",
    "# Set the number of ticks for the color bar with uniformly distributed numbers\n",
    "num_ticks = 5\n",
    "c_ticks = np.linspace(np.min(concatenated_array), np.max(concatenated_array), num_ticks)\n",
    "cbar1.set_ticks(c_ticks)\n",
    "\n",
    "# Set the fontweight and fontsize for color bar tick labels\n",
    "for t in cbar1.ax.get_yticklabels():\n",
    "    t.set_weight('normal')\n",
    "    t.set_fontsize(26)  # Increase the font size for color bar tick labels\n",
    "\n",
    "# Increase the size of numbers on axis and color bar\n",
    "plt.xticks(fontsize=26)\n",
    "plt.yticks(fontsize=26)\n",
    "\n",
    "# Increase the tick size and width of the color bar\n",
    "cbar1.ax.tick_params(axis='both', which='major', labelsize=30, width=3,  length=10)\n",
    "\n",
    "#plt.savefig('Contour_Exact.pdf', dpi=500, bbox_inches=\"tight\")\n",
    "plt.savefig('contour_exact.jpeg', dpi=500, bbox_inches=\"tight\")\n",
    "# Show the plot\n",
    "plt.show()\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "dc797c80",
   "metadata": {},
   "outputs": [],
   "source": [
    "import torch\n",
    "import numpy as np\n",
    "import matplotlib.pyplot as plt\n",
    "from matplotlib.ticker import FixedLocator\n",
    "\n",
    "# Assuming you have defined concatenated_tensor as a PyTorch tensor\n",
    "# concatenated_tensor = torch.cat((tensor1, tensor2), dim=0)\n",
    "\n",
    "# Convert concatenated_tensor to a NumPy array\n",
    "concatenated_array = concatenated_tensor.numpy()\n",
    "\n",
    "# Define custom color levels\n",
    "x = np.linspace(-1, 1, concatenated_array.shape[1])  # Replace 0 and 1 with your actual x range\n",
    "t = np.linspace(0, 1, concatenated_array.shape[0])  # Replace 0 and 1 with your actual t range\n",
    "X, T = np.meshgrid(x, t1)\n",
    "\n",
    "# Define custom color levels using the minimum and maximum from the NumPy array\n",
    "c_levels = np.linspace(np.min(concatenated_array), np.max(concatenated_array), 400)\n",
    "\n",
    "# Plot the contour with interpolated data\n",
    "plt.figure(figsize=(20, 5))\n",
    "plt.pcolormesh(T, X, concatenated_array, shading='auto', cmap='coolwarm')\n",
    "\n",
    "# Set the fontweight for axis labels to regular (not bold)\n",
    "plt.xlabel(\"$t$\", fontsize=26)\n",
    "plt.ylabel(\"$x$\", fontsize=26)\n",
    "plt.title(\"$u(x, t)$\", fontsize=26)\n",
    "\n",
    "# Set tick labels fontweight to regular (not bold) and increase font size\n",
    "plt.tick_params(axis='both', which='major', labelsize=20, width=3, length=10)\n",
    "\n",
    "# Set the fontweight for tick labels to regular (not bold)\n",
    "for tick in plt.gca().get_xticklabels() + plt.gca().get_yticklabels():\n",
    "    tick.set_weight('normal')\n",
    "\n",
    "# Set the number of ticks for x-axis and y-axis to 5\n",
    "num_ticks = 5\n",
    "x_ticks = np.linspace(np.min(T), np.max(T), num_ticks)\n",
    "y_ticks = np.linspace(np.min(X), np.max(X), num_ticks)\n",
    "\n",
    "plt.gca().xaxis.set_major_locator(FixedLocator(x_ticks))\n",
    "plt.gca().yaxis.set_major_locator(FixedLocator(y_ticks))\n",
    "\n",
    "cbar1 = plt.colorbar()\n",
    "# Set the number of ticks for the color bar with uniformly distributed numbers\n",
    "num_ticks = 5\n",
    "c_ticks = np.linspace(np.min(concatenated_array), np.max(concatenated_array), num_ticks)\n",
    "cbar1.set_ticks(c_ticks)\n",
    "\n",
    "# Set the fontweight and fontsize for color bar tick labels\n",
    "for t in cbar1.ax.get_yticklabels():\n",
    "    t.set_weight('normal')\n",
    "    t.set_fontsize(26)  # Increase the font size for color bar tick labels\n",
    "\n",
    "# Increase the size of numbers on axis and color bar\n",
    "plt.xticks(fontsize=26)\n",
    "plt.yticks(fontsize=26)\n",
    "\n",
    "# Increase the tick size and width of the color bar\n",
    "cbar1.ax.tick_params(axis='both', which='major', labelsize=30, width=3,  length=10)\n",
    "\n",
    "# Add a dotted line at t = 0.8\n",
    "plt.axvline(x=0.8, color='black', linestyle='dotted', linewidth=5)\n",
    "\n",
    "#plt.savefig('Contour_LEM_20.pdf', dpi=500, bbox_inches=\"tight\")\n",
    "plt.savefig('contour_LSTM_20.jpeg', dpi=500, bbox_inches=\"tight\")\n",
    "# Show the plot\n",
    "plt.show()\n"
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3 (ipykernel)",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.9.7"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}
